
\chapter{Syntax}

\label{chapter:syntax}   
The {\bf T} standard environment includes routines which perform
syntactic and semantic analysis of {\bf T} programs.
There are two such subsystems within {\bf T}, corresponding to the
language's two syntactic levels (see chapter \ref{chapter:semantics}).
These are the {\it reader\/} and the {\it compiler\/}.

In an attempt to make each of these subsystems as generally useful and
flexible as possible, they are not restricted to processing the language
as described in this manual.  Instead, they each operate with respect to
parameter clusters known as \iix{read tables}, in the case of the
reader, or \iix{syntax tables}, in the case of the compiler.

\section{The reader}

\label{section:reader}
The \iix{reader} is a procedure available in the standard environment as
the value of the variable {\tt READ-OBJECT}.  Conceptually, the reader
coerces a stream of characters (\ix{external representation}) to a stream of
objects (internal representations) via a mechanism
known as {\it parsing\/}.

\index{READ-OBJECT@{\tt READ-OBJECT}}
{\mbox {\tt (READ-OBJECT {\it port\/} {\it read-table\/}) $\longrightarrow$\  {\it object\/} {\rm or} {\it end-of-file\/}}}
\hfill  

\label{READ-OBJECT}
\begin{inset}{}
{\tt READ-OBJECT} employs the {\tt READ-CHAR} (page \pageref{READ-CHAR})
and {\tt UNREAD-CHAR} (page \pageref{UNREAD-CHAR}) operations in
order to parse an object according to the port's read table.

If the port is empty, the end-of-file token is returned.

{\tt READ-OBJECT} is called by the default method for the {\tt READ}
operation (page \pageref{READ}), so the reader is usually invoked
indirectly by calling
{\tt READ}, not by calling {\tt READ-OBJECT} directly.  When invoked
from {\tt READ}, the second argument to {\tt READ-OBJECT} is obtained
by calling the {\tt PORT-READ-TABLE} operation on the port.
\end{inset} 

The reader works as follows:

Any whitespace characters (space, tab, newline, carriage return, line
feed, or form feed) are read and ignored.  A non-whitespace character is
obtained; call it {\it c\/}.
\index{whitespace}

If {\it c\/} is a read-macro character, the reader invokes a specialist routine
to handle a syntactic construct introduced by the read-macro character.

If {\it c\/} is not a read-macro character, then characters are read and
saved until a {\it delimiter\/} character is read.  A delimiter character is
either a whitespace character, or one of the following: {\tt (} (left
parenthesis), {\tt }) (right parenthesis), {\tt [}, {\tt ]}, {\tt \{},
{\tt \}}, or {\tt ;} (semicolon).  If the sequence of characters beginning
with {\it c\/} and going up to but not including the delimiter is parsable
as a number, then the sequence is converted to a number, which is
returned.
Otherwise the sequence is converted to a symbol.
\index{numbers}
\index{symbols}
\index{delimiter characters}
\index{constituent characters}

The {\it escape character\/}, backslash ({$\backslash$}), may be used within a
run of constituent characters to  unusual characters in a
symbol's print name.  In this case, the escaped character (i.e. the character
following the escape character) is treated as if it were a constituent
character, and is not converted to upper case if it is a lower case
letter.  For example:
\begin{codexenv}
abc{$\backslash$};def  {\rm reads the same as}  \#[Symbol "ABC;DEF"] \\
{$\backslash$}a{$\backslash$}bcdef  {\rm reads the same as}  \#[Symbol "abCDEF"] \\
{$\backslash$}12345    {\rm reads the same as}  \#[Symbol "12345"] \\
{$\backslash$}'12345   {\rm reads the same as}  \#[Symbol "12345"'] 
\end{codexenv}


The following are standard read-macro characters:

\begin{description}
\item[{{\tt "}}]	Doublequote: introduces a string.  Characters are read until another doublequote
character is found which does not immediately follow a backslash ({$\backslash$})
and a string is returned.  Within a string, backslash acts as an escape
character, so that doublequotes and backslashes may appear in strings.
\index{strings}

\item[{'}]	Quote: '{\it object\/} reads the same as {\tt (QUOTE {\it object\/})}.
\index{QUOTE@{\tt QUOTE}}

\item[{(}]	Left parenthesis: begins a list. \index{parentheses}

\item[{)}]	Right parenthesis: ends a list or vector, and is illegal in other
contexts.

\item[{` }]	Quasiquote: see section \ref{section:quasiquote}.
	\index{quasiquote@{\tt quasiquote}}

\item[{{\tt ,}}]	Comma: this is part of the backquote syntax.

\item[{{\tt @}}]	At sign: this is part of the backquote syntax.

\item[{{\tt ;}}]	Semicolon: introduces a comment.  Characters are read and discarded
until a newline is encountered, at which point the parsing process starts over.
\label{SEMICOLON}
\index{comments}

\item[{{\tt \#}}]	Sharp-sign: another dispatch to a specialist routine is
performed according to the character following the {\tt \#}.
\end{description}

Standard sharp-sign forms:

\begin{description}
\item[{{\#$\backslash$}}]
	Character syntax.  See section \ref{character syntax}.

\item[{{\tt \#x}}]
	\ix{Hexadecimal} input.  An integer following the {\tt \#x}
is read in base 16.

\item[{{\tt \#o}}]
	Octal \index{octal} input.  An integer following the {\tt \#o} is read in base 8.

\item[{{\tt \#b}}]
	Binary input.  An integer following the {\tt \#b} is read in base 2.

\item[{{\tt \#(\ldots\ )}}]
	Vector.  The elements of a vector are read between the parentheses,
and the vector is returned.
\index{vectors}

\item[{{\tt \#[\ldots\ ]}}]
	This syntax is used for certain kinds of re-readable objects.
It also provides an alternate syntax for characters and symbols.
The brackets enclose a sequence of objects; the first should be a symbol
which keys the type of the resulting object, e.g. {\tt CHAR} or {\tt SYMBOL}.
\index{characters}\index{symbols}
For example,
\begin{codexenv}
\#[Ascii 65]       {\rm represents the same object as}  {\#$\backslash$}A \\
\#[Symbol FOO]  {\rm represents the same object as}  FOO
\end{codexenv}
This syntax is used by the printer when necessary, for example:
\begin{codexenv}
(STRING-$>$SYMBOL )  $\Longrightarrow$\   \#[Symbol ] \\
(ASCII-$>$CHAR 128)    $\Longrightarrow$\   \#[Ascii 128]
\end{codexenv}

\item[{{\tt \#\{\ldots\ \}}}]
This is the syntax used by the printer for objects which
have no reader syntax.  When the reader encounters the sequence {\tt \#\{}
it signals an error.
\end{description}

\section{Read tables and read macros}

\label{READTABLES}
Read tables \index{read tables} package a number of parameters for use by programs which
parse, generate, or otherwise manipulate external syntax of programs and
objects.  In particular, every read table contains a table which
maps characters to objects which describe their lexical
properties.

There is a standard read table which contains the standard read syntax
for all characters.  In order to define nonstandard read syntax, one
must create a new read table using {\tt MAKE-READ-TABLE}, and arrange
for {\tt READ-OBJECT} to use the new read table instead of the standard
read table, e.g. by doing {\mbox {\tt (SET (PORT-READ-TABLE \ldots\ ) \ldots\ )}}.

\index{MAKE-READ-TABLE@{\tt MAKE-READ-TABLE}}
{\mbox {\tt (MAKE-READ-TABLE {\it read-table identification\/}) $\longrightarrow$\  {\it new-read-table\/}}}
\hfill  

\begin{inset}{}
Creates a new read table which is a copy of {\it read-table\/}.
{\it Identification\/} serves for debugging purposes only.
{\tt \begin{tabbing}
(DEFINE \= *MY-READ-TABLE* \+ \\
  (MAKE-READ-TABLE STANDARD-READ-TABLE '*MY-READ-TABLE*))
\end{tabbing}}
\end{inset} 

\index{STANDARD-READ-TABLE@{\tt STANDARD-READ-TABLE}}
{\mbox {\tt STANDARD-READ-TABLE $\longrightarrow$\  {\it read-table\/}}}
\hfill  

\begin{inset}{}
The standard {\bf T} read table.
\end{inset}

\index{VANILLA-READ-TABLE@{\tt VANILLA-READ-TABLE}}
{\mbox {\tt VANILLA-READ-TABLE $\longrightarrow$\  {\it read-table\/}}}
\hfill  

\begin{inset}{}
The value of {\tt VANILLA-READ-TABLE} is a read table in which all
all graphic characters have ordinary non-read-macro constituent
syntax, whitespace characters have whitespace syntax, and
other characters (e.g. control characters) are illegal.
{\tt \begin{tabbing}
(WITH-INPUT-FROM-STRING \= (PORT " FOO () ") \+ \\
  (SET (PORT-READ-TABLE PORT) VANILLA-READ-TABLE) \\
  (LIST (READ PORT) (READ PORT))) \- \\
$\Longrightarrow$\   (FOO \#[Symbol ()])
\end{tabbing}}
\end{inset}

\index{READ-TABLE-ENTRY@{\tt READ-TABLE-ENTRY}}
{\mbox {\tt (READ-TABLE-ENTRY {\it table character\/}) $\longrightarrow$\  {\it syntax\/}}}
\hfill Settable

\begin{inset}{}
Access {\it character\/}'s read syntax in {\it table\/}.
The entry for a given character is some object which represents the
character's lexical properties, for example, whether it is
a constituent, whitespace, or read-macro character.
For read-macro characters, the entry is a procedure
for parsing the read-macro construct.
\index{read macros}

Values suitable to be stored in read tables may be obtained
by accessing existing entries in the standard read table.  For example:
{\tt \begin{tabbing}
(SET \= (READ-TABLE-ENTRY *MY-READ-TABLE* {\#$\backslash$};) \\
     \> (READ-TABLE-ENTRY STANDARD-READ-TABLE {\#$\backslash$}:))
\end{tabbing}}
makes the read syntax of semicolon in {\tt *MY-READ-TABLE*} be the
same as the standard read syntax of colon (which is a
contituent character).

To define a read macro, do
\begin{codexenv}
(SET (READ-TABLE-ENTRY {\it read-table\/} {\it character\/}) {\it procedure\/})
\end{codexenv}
where {\it procedure\/} is a procedure taking three arguments: a port,
a character, and a read-table.  The port is the port which is currently being
parsed by {\tt READ-OBJECT}.  It may be passed as the port argument
to input routines like {\tt READC} and {\tt READ-REFUSING-EOF} if the
read-macro needs to parse further characters from the input port.
The character is the character which caused the read macro to be
invoked; that is, it is the character under which the procedure is
stored in the read table. The read-table is the read table from
which the procedure was fetched (i.e. the one that was originally
passed to {\tt READ-OBJECT}. Read macros which recursively invoke the
reader will want to pass that read table as the second argument to
{\tt READ-OBJECT}.

Example:
{\tt \begin{tabbing}
(SET \= (READ-TABLE-ENTRY *MY-READ-TABLE* {\#$\backslash$}') \+ \\
     (LAMBDA \= (PORT CH RTABLE) \+ \\
       (IGNORE CH) (IGNORE RTABLE)\\
       (LIST 'QUOTE (READ-REFUSING-EOF PORT))))
\end{tabbing}}
Note that the standard read table and the vanilla read table
are immutable, and so their entries may not be changed.
\end{inset} 

\index{NOTHING-READ@{\tt NOTHING-READ}}
{\mbox {\tt NOTHING-READ $\longrightarrow$\  {\it object\/}}}
\hfill  

\begin{inset}{}
Read macros should return this object, which is treated specially
by the reader, if they want to return no object.
For example, the semi-colon (comment) read-macro might be defined as follows:
{\tt \begin{tabbing}
(SET \= (READ-TABLE-ENTRY *MY-READ-TABLE* {\#$\backslash$};) \+ \\
     (LAMBDA \= (PORT CH RTABLE) \+ \\
	(IGNORE RTABLE) \\
        (ITERATE \= LOOP () \+ \\
          (LET \= ((C (READC PORT))) \+ \\
            (COND \= ((EOF? C) C) \+ \\
                  ((CHAR= C {\#$\backslash$}NEWLINE) NOTHING-READ) \\
                  (ELSE (LOOP)))))))
\end{tabbing}}
\end{inset}

\index{DELIMITING-READ-MACRO?@{\tt DELIMITING-READ-MACRO?}}
{\mbox {\tt (DELIMITING-READ-MACRO? {\it procedure\/}) $\longrightarrow$\  {\it boolean\/}}}
\hfill Operation

\begin{inset}{}
If an object which returns true to the {\tt DELIMITING-READ-MACRO?} operation is
stored in a read table under a given character, then the reader will
treat the character as a delimiter (non-constituent) character.
By default, read-macro procedures return false to this predicate.  Thus
to make a read-macro character be a delimiting character also (as
are parentheses and semicolon in the standard read table), its
read table entry should handle this operation by returning true.
{\tt \begin{tabbing}
(SET \= (READ-TABLE-ENTRY *MY-READ-TABLE* {\#$\backslash$}$\tilde{}$) \+ \\
     (OBJECT \= (LAMBDA (PORT CH RTABLE) \+ \\
               \ldots\ ) \\
             ((DELIMITING-READ-MACRO? SELF) T)))
\end{tabbing}}
\end{inset} 

\index{MAKE-LIST-READER)@{\tt MAKE-LIST-READER})}
{\mbox {\tt (MAKE-LIST-READER) $\longrightarrow$\  {\it list-reader\/}}}
\hfill  

\begin{inset}{}
The two procedures {\tt MAKE-LIST-READER} and {\tt LIST-TERMINATOR}
can be used together to define read macros which behave syntactically
like parentheses.

Each call to {\tt MAKE-LIST-READER} returns an object which is a
procedure of two arguments called a {\it list reader.\/}  Calling
{\tt LIST-TERMINATOR} on a list reader will return another object called
its {\it list terminator.\/}

List readers and terminators are suitable for entry in read tables.
A list reader acts as a read macro which reads a sequence of objects,
terminated by a character whose read syntax is the corresponding list
terminator.  For example, the standard syntax for left and right
parentheses might be defined as follows:

{\tt \begin{tabbing}
(LET \= ((LIST-READER (MAKE-LIST-READER))) \+ \\
  (SET \= (READ-TABLE-ENTRY STANDARD-READ-TABLE {\#$\backslash$}LEFT-PAREN) \+ \\
       LIST-READER) \- \\
  (SET (READ-TABLE-ENTRY STANDARD-READ-TABLE {\#$\backslash$}RIGHT-PAREN) \+ \\
       (LIST-TERMINATOR LIST-READER)))
\end{tabbing}}

Like any read-macro procedure, a list reader is a procedure of two
arguments.  The first argument must be a port, and the second is
ignored.  Thus instead of being stored in a read table, it may be
called from another read-macro procedure.  For example, the following
makes {\tt [\ldots\ ]} an alternative read syntax for vectors:
{\tt \begin{tabbing}
(LET \= ((LIST-READER (MAKE-LIST-READER))) \+ \\
  (SET \= (READ-TABLE-ENTRY *MY-READ-TABLE* {\#$\backslash$}LEFT-BRACKET) \+ \\
       (OBJECT \= (LAMBDA \= (PORT CH RTABLE) \+ \+ \\
		 (IGNORE RTABLE) \\
                 (LIST-$>$VECTOR (LIST-READER PORT CH))) \- \\
               ((DELIMITING-READ-MACRO? SELF) T))) \- \- \\
  (SET (READ-TABLE-ENTRY *MY-READ-TABLE* {\#$\backslash$}RIGHT-BRACKET) \+ \\
       (LIST-TERMINATOR LIST-READER)))
\end{tabbing}}

List readers and terminators handle the {\tt DELIMITING-READ-MACRO?}
operation by returning true.
\end{inset} 

\index{LIST-TERMINATOR@{\tt LIST-TERMINATOR}}
{\mbox {\tt (LIST-TERMINATOR {\it list-reader\/}) $\longrightarrow$\  {\it list-terminator\/}}}
\hfill  

\begin{inset}{}
Given a list reader, returns its list terminator.  See {\tt LIST-READER},
above.
\end{inset} 

\section{Standard compiler}


A \iix{compiler} is a procedure which accepts an expression and a
syntax table, and returns a {\it compiled code\/} object.  A compiled
code object may be executed in a given environment.  Note that
the term ``compiler'' is used in a technical sense
and encompasses not only compilers such as {\sc orbit}
(section \ref{COMPILE-FILE}) which
produce machine instructions, but also programs such as the standard
compiler (which is called by {\tt EVAL}) which operate internally by
producing intermediate code or by interpreting source code directly.
Often programs like these are called {\it interpreters\/} instead of
{\it compilers.\/}

A given {\bf T} implementation may have several compilers.
{\tt STANDARD-COMPILER} should be one of these compilers.
{\bf T} 3.1 also provides a compiler called {\sc orbit}, which is
described in section \ref{COMPILE-FILE}.

\index{EVAL@{\tt EVAL}}
{\mbox {\tt (EVAL {\it expression\/} {\it environment\/}) $\longrightarrow$\  {\it object\/}}}
\hfill  

\begin{inset}{}
Evaluates {\it expression\/} in {\it environment\/}.  Evaluation is performed as
a two-stage process: first, the standard compiler compiles the
expression, producing a compiled code object; then the compiled code
object is invoked in the given environment.
{\tt \begin{tabbing}
(EVAL \= {\it expression\/} {\it environment\/}) \\
  \> $\equiv$ \\
(RUN-COMPILED-CODE \= (STANDARD-COMPILER \= {\it expression\/} \\
                                      \> \> (ENV-SYNTAX-TABLE {\it environment\/})) \\
                   \> {\it environment\/})
\end{tabbing}}

The evaluation semantics have been extended to allow the
valuation of forms whose {\mbox {\tt car}}'s are syntax descriptors.
such a form is interpreted just as if it were a form whose {\mbox {\tt car}}
was a symbol whose syntax table entry was the syntax descriptor.
For example,

{\tt \begin{tabbing}
(DEFINE-LOCAL-SYNTAX \= (FOO X) \\
 \> ` (,(SYNTAX-TABLE-ENTRY STANDARD-SYNTAX-TABLE 'LAMBDA) () ,X)) \\

((FOO 5)) $\Longrightarrow$\  5
\end{tabbing}}

\index{expression syntax}

This feature allows control over binding time for reserved words.
For example, a syntax descriptor such as {\tt FOO}, above, can
be sure that its expansion will be treated as an expression
that evaluates to a closure, regardless of what the syntax table
entry for the symbol {\mbox {\tt lambda}} is when the expansion
is evaluated or otherwise analyzed.
\end{inset} 

\index{STANDARD-COMPILER@{\tt STANDARD-COMPILER}}
{\mbox {\tt (STANDARD-COMPILER {\it expression\/} {\it syntax-table\/}) $\longrightarrow$\  {\it compiled-code\/}}}
\hfill  

\label{STANDARD-COMPILER}
\begin{inset}{}
Compiles {\it expression\/}. {\bf T} may provide several
compilers, of which {\tt STANDARD-COMPILER} will be the one which is
invoked by {\tt EVAL}.
\end{inset} 

\index{RUN-COMPILED-CODE@{\tt RUN-COMPILED-CODE}}
{\mbox {\tt (RUN-COMPILED-CODE {\it compiled-code\/} {\it environment\/}) $\longrightarrow$\  {\it object\/}}}
\hfill  

\begin{inset}{}
Invokes a compiled code object.
\end{inset} 

\section{Syntax Tables}


\label{section:syntaxTables}   
\index{syntax tables}
\index{reserved words}
\index{special forms}
A syntax table maps symbols to \iix{syntax descriptors}.  Every syntax
descriptor is itself either a macro expander, or a unique token
identifying a primitive special form type.

Every locale has an associated syntax table.  A locale's syntax table
contains definitions of special forms which are local to the locale.  Each
such syntax table inherits entries lexically from the syntax tables
of enclosing locales.

{\it Macros\/}\index{macros} provide a mechanism for extending the syntax of {\bf T}
by means of source-to-source transformations.
As in many Lisp dialects, the macro facility in {\bf T} provides a powerful
tool for amplifying the expressiveness of the language.  But like any
powerful tool, macros may be abused.  They may easily lead to programs
that are very hard to understand.

Macros are defined by entering syntax descriptor objects known as
\iix{macro expanders} into syntax tables; see
{\tt SYNTAX-TABLE-ENTRY} and {\tt DEFINE-SYNTAX}, below.
Macros may also be defined locally to a file or expression using
{\tt DEFINE-LOCAL-SYNTAX} or {\tt LET-SYNTAX}.

Procedure integration is preferable to the use of macros in situations
where either would be applicable.  See {\tt DEFINE-INTEGRABLE}, page
\pageref{section:defineIntegrable}.

\index{ENV-SYNTAX-TABLE@{\tt ENV-SYNTAX-TABLE}}
{\mbox {\tt (ENV-SYNTAX-TABLE {\it environment\/}) $\longrightarrow$\  {\it syntax-table\/}}}
\hfill  

\begin{inset}{}
Returns the syntax table associated with {\it environment\/}.
\end{inset} 

\index{MAKE-SYNTAX-TABLE@{\tt MAKE-SYNTAX-TABLE}}
{\mbox {\tt (MAKE-SYNTAX-TABLE {\it syntax-table\/} {\it identification\/}) $\longrightarrow$\  {\it syntax-table\/}}}
\hfill  

\begin{inset}{}
Creates a new syntax table inferior to the given syntax table.
Note that syntax tables are created implicitly by {\tt MAKE-LOCALE}
(page \pageref{MAKE-LOCALE}).
\end{inset} 

\index{STANDARD-SYNTAX-TABLE@{\tt STANDARD-SYNTAX-TABLE}}
{\mbox {\tt STANDARD-SYNTAX-TABLE $\longrightarrow$\  {\it syntax-table\/}}}
\hfill  

\begin{inset}{}
A syntax table with entries for all standard {\bf T} reserved words.
\begin{codexenv}
STANDARD-SYNTAX-TABLE  $\equiv$  (ENV-SYNTAX-TABLE-ENTRY STANDARD-ENV)
\end{codexenv}
\end{inset} 


\index{SYNTAX-TABLE-ENTRY@{\tt SYNTAX-TABLE-ENTRY}}
{\mbox {\tt (SYNTAX-TABLE-ENTRY {\it syntax-table\/} {\it symbol\/}) $\longrightarrow$\  {\it descriptor\/} {\rm or} {\it false\/}}}
\hfill Settable

\label{SYNTAX-TABLE}
\begin{inset}{}
Accesses the syntax descriptor associated with {\it symbol\/} in
{\it syntax-table\/}.  Returns false if there is no such entry.
{\tt \begin{tabbing}
(SYNTAX-TABLE-ENTRY STANDARD-SYNTAX-TABLE 'QUOTE)  $\Longrightarrow$\   \#\{Syntax QUOTE\}
\\
(SYNTAX-TABLE-ENTRY STANDARD-SYNTAX-TABLE 'CAR)    $\Longrightarrow$\   {\it false}
\end{tabbing}}
Syntax table entries may be created or altered using
{\mbox {\tt (SET (SYNTAX-TABLE-ENTRY \ldots\ ) \ldots\ )}}
or by using {\tt DEFINE-SYNTAX}.  On assignment, {\it descriptor\/} may
be false, in which case {\it symbol\/} loses any syntax table entry it
may have had.  This allows it to be bound as a variable using
{\tt DEFINE} or {\tt LET}, for example.
\end{inset} 

\section{Defining syntax}


\index{DEFINE-SYNTAX@{\tt DEFINE-SYNTAX}}
{\mbox {\tt (DEFINE-SYNTAX {\it symbol\/} {\it descriptor\/}) $\longrightarrow$\  {\it undefined\/}}}
\hfill  
\\ {\mbox {\tt (DEFINE-SYNTAX ({\it symbol\/} . {\it vars\/}) . {\it body\/}) $\longrightarrow$\  {\it undefined\/}}}

\begin{inset}{} 
Sets {\it symbol\/}'s syntax table entry in the syntax table of the
environment in which the {\tt DEFINE-SYNTAX} form is being evaluated.
The second form is an abbreviation for an equivalent expression
of the first form involving {\tt MACRO-EXPANDER}:
{\tt \begin{tabbing}
(DEFINE-SYNTAX \= ({\it symbol\/} . {\it variables\/}) . {\it body\/}) \\
  \> $\equiv$ \\
(DEFINE-SYNTAX {\it symbol\/} \\
  \> (MACRO-EXPANDER ({\it symbol\/} . {\it variables\/}) . {\it body\/}))
\end{tabbing}}
Macros and {\tt MACRO-EXPANDER} are explained below.

As with {\tt (SET (SYNTAX-TABLE-ENTRY \ldots\ ) \ldots\ )}, {\it descriptor\/} may
be false, in which case {\it symbol\/} loses any syntax table entry it
may have had.  This allows it to be bound as a variable using
{\tt DEFINE} or {\tt LET}, for example.

Note that {\tt DEFINE-SYNTAX} forms have no effect
at compile time.  Using them indiscriminately may lead to code
which behaves differently depending on what compiler is being used.
For example, a use of the special form defined by a {\tt DEFINE-SYNTAX}
form later on in the same file in which the {\tt DEFINE-SYNTAX} form
occurs may be seen as a valid special form reference by the standard
compiler, but may be treated as a call by {\sc orbit}.

{\tt \begin{tabbing}
(DEFINE-SYNTAX \= (REPEAT N . CODE) \+ \\
  ` (LET \= ((COUNT ,N) \+ \\
         (THUNK (LAMBDA () ,@CODE))) \\
     (DO \= ((COUNT COUNT (- COUNT 1))) \+ \\
         (($<$= COUNT 0) NIL) \\
       (THUNK))))
\end{tabbing}}
\end{inset}

\section{Local syntax}


Reserved words may be defined at compile time using {\tt LET-SYNTAX}
and {\tt DEFINE-LOCAL-SYNTAX}.  Syntax defined this way is called
\iix{local syntax} and is in effect only at compile time, not at run
time.

Local syntax is block structured, much as variables are.  The outermost
local syntax contour is the point at which a compiler is invoked,
which usually means a file boundary.  Inner contours are introduced
by {\tt LET-SYNTAX} forms.

Put another way, a local syntax table is created whenever a compiler
is invoked ({\tt LOAD}, {\tt COMPILE-FILE}, {\tt EVAL}) and whenever a
{\tt LET-SYNTAX} form is compiled.  Entries are created in a local
syntax table at compile time for syntax defined initially by the
{\tt LET-SYNTAX} form and later when the compiler encounters
{\tt DEFINE-LOCAL-SYNTAX} forms.  The syntax table is used at compile
time and is otherwise unavailable.

\index{LET-SYNTAX@{\tt LET-SYNTAX}}
{\mbox {\tt (LET-SYNTAX {\it specs\/} . {\it body\/}) $\longrightarrow$\  {\it value-of-body\/}}}
\hfill  

\begin{inset}{}
Defines macros locally to {\it body\/}.  Yields the value of {\it body\/},
an implicit block.  Each {\it spec\/} should be either
\begin{codexenv}
({\it symbol\/} {\it descriptor\/})
\end{codexenv}
or
\begin{codexenv}
(({\it symbol\/} . {\it vars\/}) . {\it body\/})
\end{codexenv}
in analogy to {\tt DEFINE-SYNTAX}.

The {\it descriptor\/} and {\it body\/} forms in {\it specs\/} will not necessarily
run in an environment which is at all related to the environment in
which the program in which the {\tt LET-SYNTAX} form occurred will
be run, because compilation may occur independently of execution.
{\sc orbit} evaluates syntax-descriptors in the
{\mbox {\tt env-for-syntax-definition}} associated with the syntax
table from which the descriptor was obtained, e.g. {\mbox {\tt (tc-syntax-table)}}.
The standard compiler uses the
locale with which the syntax table passed to it is associated.
This is implementation-dependent, and subject to change.  For this reason,
it is best to write local macros in such a way that no free variables
or special forms are used, other than those in the standard system
environment, that is, those defined to be part of the {\bf T} language.

This disclaimer does not apply to the {\it body\/} of the {\tt LET-SYNTAX} form,
which is evaluated (except for syntax) exactly as if the {\tt LET-SYNTAX}
expression were a {\tt BLOCK} expression.
{\tt \begin{tabbing}
(LET-SYNTAX \= ((KWOTE (SYNTAX-TABLE-ENTRY \= STANDARD-SYNTAX-TABLE \\
                                        \> \> 'QUOTE))) \\
  \> (KWOTE (A B C)))\index{KWOTE@{\tt KWOTE}} \\
\> $\Longrightarrow$\   (A B C)
\end{tabbing}}

{\tt \begin{tabbing}
(LET-SYNTAX ((SET NIL)) (LET ((SET LIST) (X 5)) (SET X 8)))  $\Longrightarrow$\   (5 8) \\

(LET-SYNTAX (((MAC X) ` '(X = ,X))) (MAC Y))  $\Longrightarrow$\   (X = Y)
\end{tabbing}}
\end{inset} 


\index{DEFINE-LOCAL-SYNTAX@{\tt DEFINE-LOCAL-SYNTAX}}
{\mbox {\tt (DEFINE-LOCAL-SYNTAX {\it symbol\/} {\it descriptor\/}) $\longrightarrow$\  {\it undefined\/}}}
\hfill Special form
\\ {\mbox {\tt (DEFINE-LOCAL-SYNTAX ({\it symbol\/} . {\it vars\/}) . {\it body\/}) $\longrightarrow$\  {\it undefined\/}}}

\begin{inset}{} 
{\tt DEFINE-LOCAL-SYNTAX} defines syntax locally to the body of the
nearest enclosing {\tt LET-SYNTAX} form, or, if the
{\tt DEFINE-LOCAL-SYNTAX} does not
appear inside a {\tt LET-SYNTAX} form, then to the file or outermost
expression in which it occurs.  Forward references are not defined
to work; the {\tt DEFINE-LOCAL-SYNTAX} form should appear prior to any use of
{\it symbol\/} as a reserved word.

The syntax of {\tt DEFINE-LOCAL-SYNTAX} is analogous to that of
{\tt DEFINE-SYNTAX}.

In general, {\tt DEFINE-LOCAL-SYNTAX} should be used for syntax which is
to be available only within the file in which it occurs.  If
a syntax definition is needed for several files, then they
should be made available in some locale's syntax table by evaluating
{\tt DEFINE-SYNTAX} forms in that locale, and then that locale's syntax table
should be used when compiling or loading the file (see the {\tt SYNTAX-TABLE}
file header clause, page \pageref{SYNTAX-TABLE}).

    \begin{inset}{Note:}
    To ease incremental debugging, the standard compiler 
    causes syntax defined with {\tt DEFINE-LOCAL-SYNTAX} to be
    retained indefinitely; that is, they are entered into the syntax
    table of the locale which was passed to {\tt LOAD}.  Programs should
    not rely on this feature,
    however, or code may behave differently when compiled.
    \end{inset}
\end{inset}

\section{Macro expanders}


\index{MACRO-EXPANDER@{\tt MACRO-EXPANDER}}
{\mbox {\tt (MACRO-EXPANDER ({\it identification\/} . {\it variables\/}) . {\it body\/}) $\longrightarrow$\  {\it macro-expander\/}}}
\hfill Special form

\begin{inset}{}
Yields a macro expander.  A macro expander is a kind of syntax
descriptor, and may therefore be stored in a syntax table.  When a
compiler using a symbol table {\it S\/} encounters a form whose car is
a symbol, and the entry in {\it S\/} for that symbol is the object yielded
by a {\tt MACRO-EXPANDER}-expression, then the macro expander
is invoked; that is, its
{\it variables\/} are bound to the rest of form (as with one level of
{\tt DESTRUCTURE} binding), the {\it body\/} (an implicit block) is evaluated,
and the value is returned to the compiler.  The compiler then compiles that
form in place of the original one.

The lexical context of {\it body\/} is that of the {\tt MACRO-EXPANDER} form
(augmented by the bindings of {\it variables\/}, of course), as with
{\tt LAMBDA}.
{\tt \begin{tabbing}
(DEFINE M (MACRO-EXPANDER (FOO X Y Z) ` (LIST 'FIRST ',X ,Y ,Z))) \\
(INVOKE-MACRO-EXPANDER \= M '(BAR QUOTED (+ 1 2) (* 3 4))) \\
  \> $\Longrightarrow$\   (LIST 'FIRST 'QUOTED  (+ 1 2) (* 3 4)) \\

(DEFINE L (MAKE-LOCALE STANDARD-ENV NIL)) \\
(SET (SYNTAX-TABLE-ENTRY (ENV-SYNTAX-TABLE L) 'BAR) M) \\

(EVAL '(BAR QUOTED (+ 1 2) (* 3 4)) L)  $\Longrightarrow$\   (FIRST QUOTED 3 12) \\

(DEFINE-SYNTAX \= FOO \+ \\
  (MACRO-EXPANDER \= (FOO THING FORM) \+ \\
    ` (LIST ,FORM ',THING))) \- \- \\

(FOO (CONS 1 2) (CONS 3 5))  $\Longrightarrow$\   ((3 . 5) (CONS 1 2))
\end{tabbing}}

{\tt DESTRUCTURE} (page \pageref{DESTRUCTURE}) and
quasiquote (page \pageref{section:quasiquote}) are useful in writing
macro expansion procedures, the first for taking apart the
form which is to be expanded, the second for constructing the resultant code
from templates.

Note that for a macro definition to take effect at compile time, it
must either be present in the syntax table being used by the
compiler (see page \pageref{SYNTAX-TABLE}), or defined locally
using {\tt LET-SYNTAX} or {\tt DEFINE-LOCAL-SYNTAX}.
\end{inset} 

\index{MACRO-EXPANDER?@{\tt MACRO-EXPANDER?}}
{\mbox {\tt (MACRO-EXPANDER? {\it descriptor\/}) $\longrightarrow$\  {\it boolean\/}}}
\hfill  

\begin{inset}{}
Returns true if {\it descriptor\/}, which must be a syntax descriptor,
is a macro expander.
\begin{codexenv}
(MACRO-EXPANDER? (MACRO-EXPANDER (FOO X) X))  $\Longrightarrow$\   {\it true}
\end{codexenv}
\end{inset} 

\index{INVOKE-MACRO-EXPANDER@{\tt INVOKE-MACRO-EXPANDER}}
{\mbox {\tt (INVOKE-MACRO-EXPANDER {\it descriptor\/} {\it form\/}) $\longrightarrow$\  {\it new-form\/}}}
\hfill  

\begin{inset}{}
Invokes the macro expansion procedure for {\it descriptor\/}, which must
be a macro expander.  (See {\tt MACRO-EXPANDER}, above.)
{\tt \begin{tabbing}
(INVOKE-MACRO-EXPANDER \= (MACRO-EXPANDER (FOO X) ` (LAMBDA () ,X)) \\
                       \> ` (BAZ (+ 1 2))) \\
  \> $\Longrightarrow$\  \\
(LAMBDA () (+ 1 2))
\end{tabbing}}
\end{inset} 

\index{MACRO-EXPAND@{\tt MACRO-EXPAND}}
{\mbox {\tt (MACRO-EXPAND {\it form syntax-table\/}) $\longrightarrow$\  {\it new-form\/}}}
\hfill  

\begin{inset}{}
Performs one macro expansion on the {\it form\/}, if it is a list whose
car is a symbol, there is an entry in the given {\it syntax-table\/} for
that symbol, and that entry is a macro expander.
\end{inset} 
